package com.maze.game.model
{
	import com.greensock.TweenLite;
	import com.greensock.easing.Strong;
	import com.maze.game.event.GameEvent;
	import com.maze.game.model.base.BaseExit;
	import com.maze.game.model.entity.Entity;
	
	import flash.display.Loader;
	import flash.display.Sprite;
	import flash.events.Event;
	import flash.events.KeyboardEvent;
	import flash.net.URLLoader;
	import flash.net.URLRequest;
	import flash.ui.Keyboard;
	
	public class Avatar extends Entity
	{
		private var baseWidth:uint;
		private var baseHeight:uint;
		private var avatarWidth:uint = 23;
		private var avatarHeight:uint = 23;
		private var goDirection:uint = 0;
		private var keysDirecctionCodeDown:Array = [];
		private var speed:uint = 4;
		private var horizontalStep:Number = 0;
		private var verticalStep:Number = 0;
		private var baseExit:BaseExit;
		private var throughExit:Boolean = false;
		private var icon:Sprite;
		private var image:Sprite;
		
		public function Avatar(baseWidth:uint,baseHeight:uint)
		{
			super();
			this.baseWidth = baseWidth;
			this.baseHeight = baseHeight;
			build();
			addEventListener(Event.ADDED_TO_STAGE, stageInit);
		}

		private function stageInit(evt:Event):void
		{
			removeEventListener(Event.ADDED_TO_STAGE, stageInit);
			configureEntityListener();
		}
		
		private function build():void
		{
			icon = new Sprite;
			icon.graphics.beginFill(0x883399);
			icon.graphics.drawCircle(avatarWidth/2,avatarHeight/2,avatarWidth/2);
			icon.graphics.endFill();
			addChild(icon);
			icon.x = baseWidth/2 - icon.width/2;
			icon.y = baseHeight/2 - icon.height/2;
			loadImage();
		}
		
		private function loadImage():void
		{
			image = new Sprite();
			addChild(image);
			var loader:Loader = new Loader();
			loader.contentLoaderInfo.addEventListener(Event.COMPLETE, imageComplete);
			loader.load(new URLRequest("avatar-alf.jpeg"));
			image.addChild(loader);
		}

		private function imageComplete(evt:Event):void
		{
			image.width = avatarWidth;
			image.height = avatarHeight;
			image.x = baseWidth/2 - avatarWidth/2;
			image.y = baseHeight/2 - avatarHeight/2;
		}

		private function configureEntityListener():void
		{
			stage.addEventListener(KeyboardEvent.KEY_DOWN, entityKeyDown);
			stage.addEventListener(KeyboardEvent.KEY_UP, entityKeyUp);
		}
		
		private function removeEntityListener():void
		{
			removeEventListener(Event.ENTER_FRAME, entityMove);
			stage.removeEventListener(KeyboardEvent.KEY_DOWN, entityKeyDown);
			stage.removeEventListener(KeyboardEvent.KEY_UP, entityKeyUp);
		}
		private function entityKeyDown(evt:KeyboardEvent):void
		{
			goDirection = getDirectionCode(evt);
			if(keysDirecctionCodeDown.indexOf(goDirection)==-1 && goDirection>0)
			{
				keysDirecctionCodeDown.push(goDirection);
			}
			if(keysDirecctionCodeDown.length==0) return;
			addEventListener(Event.ENTER_FRAME, entityMove);
		}
		
		private function getDirectionCode(evt:KeyboardEvent):uint
		{
			var keyCode:uint = 0;
			if (evt.keyCode == Keyboard.DOWN || evt.keyCode == 83)
			{
				keyCode = Keyboard.DOWN;
			}
			if (evt.keyCode == Keyboard.UP || evt.keyCode == 87)
			{
				keyCode = Keyboard.UP;
			}
			if (evt.keyCode == Keyboard.LEFT || evt.keyCode == 65)
			{
				keyCode = Keyboard.LEFT;
			}
			if (evt.keyCode == Keyboard.RIGHT || evt.keyCode == 68)
			{
				keyCode = Keyboard.RIGHT;
			}
			return keyCode;
		}
		
		private function entityKeyUp(evt:KeyboardEvent):void
		{
			goDirection = 0;
			var directionStop:uint = getDirectionCode(evt);
			entityStop(directionStop);
			if(keysDirecctionCodeDown.indexOf(directionStop)>-1)
			{
				keysDirecctionCodeDown.splice(keysDirecctionCodeDown.indexOf(directionStop),1);
			}
			if(keysDirecctionCodeDown.length>0) return;
			removeEventListener(Event.ENTER_FRAME, entityMove);
			walkOff();
		}
		
		private function entityMove(evt:Event):void
		{
			if (goDirection == Keyboard.DOWN)
			{
				verticalStep = speed;
			}
			if (goDirection == Keyboard.UP)
			{
				verticalStep = -speed;
			}
			if (goDirection == Keyboard.LEFT)
			{
				horizontalStep = -speed;
			}
			if (goDirection == Keyboard.RIGHT)
			{
				horizontalStep = speed;
			}
			var oldX:Number = x;
			var newX:Number = (checkAreaX(x+horizontalStep) || throughExit)?horizontalStep:0;
			x += newX;
			if(getObstacle())
				x = oldX;
			var oldY:Number = y;
			var newY:Number = (checkAreaY(y+verticalStep) || throughExit)?verticalStep:0;
			y += newY;
			if(getObstacle())
				y = oldY;
			if(this.hitTestObject(baseExit))
			{
				throughExit = true;
			}
			if(throughExit && (!checkAreaX(x) || !checkAreaY(y)))
			{
				exitShow();
			}
		}
		
		private function entityStop(directionCode:uint):void
		{
			if (directionCode == Keyboard.DOWN || directionCode == Keyboard.UP)
			{
				verticalStep = 0;
			}
			if (directionCode == Keyboard.LEFT || directionCode == Keyboard.RIGHT)
			{
				horizontalStep = 0;
			}
		}

		private function walkOff():void
		{
			goDirection = 0;
		}
		
		public function setBaseExit(value:BaseExit):void
		{
			baseExit = value;
		}
		
		private function exitShow():void
		{
			walkOff();
			removeEntityListener();
			dispatchEvent(new GameEvent(GameEvent.WIN));
		}
	}
}